THREE におけるベジェ曲線の結合
※ベジェの結合は一定だが、ベジェの中身はでの移動は座標的には一定じゃない。
ベジェ曲線が複数存在しており、0-1で、移動距離が一定のベジェ曲線描画を行いたかった。
onuma.icon ベジェ曲線をくっつけただけなんですね。最初mixするのかと思ってびっくりした。。。
ArakiTakaki.icon複数のベジェをミックスして単一ベジェに直すのは確かにびっくりしますね・・・w(無理)
リアルタイムで求めるのは結構重たそう(印象)なため
あらかじめルートを求める(getSpacedPointsとかにしたほうがいい)
ワーカーへの切り出し
上記のどちらか(あるいは両方)行ったほうがUIイベントをブロックしなくて済み良いかもしれない。
実装
code:typescript
/**
* bezierの結合
* @param curveList
*/
export const createCurvePoint = <T extends THREE.Vector>(
curveList: THREE.Curve<T>[]
): (point: number) => T => {
const totalLength = curveList.reduce((n, bezier) => n + bezier.getLength(), 0);
const bezierLengthPointList = curveList.map((bezier) => bezier.getLength() / totalLength);
/**
* @param point 0-1 0: 開始地点 1: 終了地点
*/
return (point: number): T => {
const calcPoint, calcIndex = ((): number, number => {
let currentPoint = point;
for(let i = 0; i < bezierLengthPointList.length; i++) {
const bezierLengthPoint = bezierLengthPointListi;
if (currentPoint - bezierLengthPoint <= 0) {
return currentPoint / bezierLengthPoint, i;
}
currentPoint = currentPoint - bezierLength;
}
return 1, bezierLengthPoint.length - 1;
})();
return curveListcalcIndex.getPoint(calcPoint); // getPointAtを行うと距離も加味してくれるため、等速となる。
};
};
スナップショット
code:typescript
const testCase = [
new THREE.CubicBezierCurve3(
new THREE.Vector3(0, 0, 0),
new THREE.Vector3(1, 1, 1),
new THREE.Vector3(0, 0, 0),
new THREE.Vector3(1, 1, 1),
),
new THREE.CubicBezierCurve3(
new THREE.Vector3(1, 1, 1),
new THREE.Vector3(2, 2, 2),
new THREE.Vector3(1, 1, 1),
new THREE.Vector3(2, 2, 2),
),
new THREE.CubicBezierCurve3(
new THREE.Vector3(2, 2, 2),
new THREE.Vector3(2.5, 2.5, 2.5),
new THREE.Vector3(2, 2, 2),
new THREE.Vector3(2.5, 2.5, 2.5),
),
];
const getPoint = createCurvePoint<THREE.Vector3>(testCase);
it('snapshot', () => {
const max = 20;
const vecList = new Array(max)
.fill(1)
.map((_, index) => getPoint(index / (max - 1)))
.map(vec3ToCSVParser)
.join('\n');
expect(vecList).toMatchSnapshot();
});
出力結果
https://gyazo.com/e1fc9764968f251f2468238a9015e289
所感
最後の結果は他の結果と比べ遷移する値が、2分の1になっておりよい感じですね。
あとグラフ描画とかは素直にスプレッドシート使えば良いなと思いました。
よい感じにサラッと出力できるグラフ描画系ツールとかおしえてください。。。
今回threeで行なったが、別にベジェ曲線ならそう言うライブラリある気がする。
#Three.js #CubicBezier
Created by ArakiTakaki